﻿<!DOCTYPE html>
<html>
<head>
  <title>蜘蛛纸牌</title>
  <meta charset="utf-8"/>
  <meta content="IE=edge,chrome=1" http-equiv="X-UA-Compatible"/>
  <meta content="webkit" name="renderer"/>
  <meta content="Title" name="apple-mobile-web-app-title"/>
  <meta content="yes" name="apple-mobile-web-app-capable"/>
  <meta content="black" name="apple-mobile-web-app-status-bar-style"/>
  <meta content="True" name="HandheldFriendly"/>
  <meta content="width=device-width, initial-scale=0.9" name="viewport">
  <meta content="DoubleAm的博客,贺雄彪的博客,贺雄彪,鲸落oh,江湖小栈" name="description">
  <meta Content="DoubleAm的博客,贺雄彪的博客,贺雄彪,鲸落oh,江湖小栈" name="keywords">
  <meta content="DoubleAm" name="author">
  <link href="/images/favicon.png" rel="shortcut icon">
  <link rel="stylesheet" href="css/public.css">
  <script src="js/jquery.min.js"></script>
</head>
<body style="overflow: hidden;">
<a href="/" style="position: fixed;top:0;left:0;z-index: 9999;">回到首页</a>
<div class="gameView" id="gameView" style="margin: 0 auto!important;">
  <div class="gameBg"></div>
  <div class="pokerBox" id="pokerBox"></div>
</div>

<script type="text/javascript">
  $('#pokerBox').on('mousedown', 'img', function (event) {
    event.preventDefault();
  })

  var pickLeft = pickTop = 0;
  var pickObj = null;
  $('body').on('mousedown', '#pokerBox .pokerLine .pokerLi', function (event) {
    var check = checkCanPickPoker(this);
    if (check.state) {
      var e = event || window.event;
      pickLeft = e.offsetX;
      pickTop = e.offsetY;
      pickObj = $(this);

      var groupTop = Number($(this).attr('groupTop'));
      var html = '';
      $(this).closest('.pokerLine').find('.pokerLi').each(function () {
        if ($(this).attr('groupTop') >= groupTop) {
          html += $(this).prop('outerHTML');
          $(this).attr('state', 'move');
        }
      });

      var itLeft = e.clientX - pickLeft;
      var itTop = e.clientY - pickTop;
      $('#pokerBox .pokerMoveGroup').show().css({
        top: itTop,
        left: itLeft,
      }).html(html);
    } else {
      gAlert({
        txt: '该牌不允许被拖动',
      });
    }
  }).on('mousemove', function (event) {
    if (pickObj) {
      var e = event || window.event;
      var itLeft = e.clientX - pickLeft;
      var itTop = e.clientY - pickTop;
      $('#pokerBox .pokerMoveGroup').css({
        top: itTop,
        left: itLeft,
      })
    }
  }).on('mouseup', function (event) {
    if (pickObj) {
      var endLeft = Number($('#pokerBox .pokerMoveGroup').css('left').replace('px', '')) + 50;
      var leftKb = $('#gameView')[0].offsetLeft;
      var range = 0;
      if (endLeft <= leftKb + 120 + 10) { // 处于第一列
        range = 1;
      } else if (endLeft >= leftKb + 120 * 9 + 10) { // 处于最后一列
        range = 10;
      } else {
        range = Math.ceil((endLeft - leftKb) / 120);
      }

      var moveCard = pickObj;
      var endCard = $('#pokerBox .pokerLine[group="' + range + '"] .pokerLi:last');

      if (endCard.length > 0) {
        var moveCardSplit = moveCard.attr('card').split('-');
        var endCardSplit = endCard.attr('card').split('-');
        // if(moveCardSplit[0]==endCardSplit[0]&&moveCardSplit[1]==endCardSplit[1]-1){
        if (moveCardSplit[1] == endCardSplit[1] - 1) {
          $('#pokerBox .pokerLine[group="' + range + '"]').append($('#pokerBox .pokerMoveGroup').html());
          $('#pokerBox .pokerLine[group="' + range + '"] .pokerLi').attr({
            grouptop: function () {
              return $(this).index() + 1
            },
            groupleft: range,
          })
          $('#pokerBox .pokerLine .pokerLi[state="move"]').remove();
        }
      } else {
        $('#pokerBox .pokerLine[group="' + range + '"]').append($('#pokerBox .pokerMoveGroup').html());
        $('#pokerBox .pokerLine[group="' + range + '"] .pokerLi').attr({
          grouptop: 1,
          groupleft: range,
        })
        $('#pokerBox .pokerLine .pokerLi[state="move"]').remove();
      }

      $('#pokerBox .pokerLine .pokerLi[state="move"]').removeAttr('state');

      $('#pokerBox .pokerMoveGroup').hide().css({
        top: 0,
        left: 0,
      }).empty();
      pickLeft = pickTop = 0;
      pickObj = null;
    }

    checkNoOpenPoker(); // 检测并翻开没有翻开的扑克
    checkDonePoker(); // 检测是否可以直接收取正确排序的卡牌
  })

  $('#pokerBox').on('click', '.pokerDeposit', function () {
    keepSendPoker();
  })

  // 初始化页面布局
  function initView() {
    var html = html2 = '';
    for (var i = 1; i <= 10; i++) {
      html += '<div class="pokerBr" style="left: ' + (120 * i - 100) + 'px" group="' + i + '"></div>';
      html2 += '<div class="pokerLine" style="left: ' + (120 * i - 100) + 'px" group="' + i + '"></div>';
    }
    var html3 = '<div class="pokerDeposit"></div>'; // 牌堆
    var html4 = '<div class="pokerMoveGroup"></div>'; // 移动牌组
    var html5 = '<div class="pokerDoneGroup"></div>'; // 完成牌组
    $('#pokerBox').html(html + html2 + html3 + html4 + html5);
  }

  // 生成随机扑克牌数组
  var pokerData = {
    type: ['a', 'b', 'c', 'd'], // [a 方片] [b 梅花] [c 黑桃] [d 红桃]
    num: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13],
  };
  var pokerAllCount = 0;
  var pokerAllPet = [];
  var pokerSendNum = 0;
  var pokerDifficult = 1; // [1 简单（单色）] [2 中等（双色）] [3 困难（四色）]
  function initRandomPoker() {
    pokerAllCount = 0;
    pokerAllPet = [];
    pokerSendNum = 0;
    for (var i = 1; i <= pokerData.type.length; i++) {
      for (var t = 1; t <= pokerData.num.length; t++) {
        var d = pokerData.type[i - 1] + '-' + pokerData.num[t - 1];
        pokerAllPet.push(d, d);
      }
    }
    // console.log(pokerAllPet);
    pokerAllCount = pokerAllPet.length;
    pokerAllPet = shuffle(pokerAllPet);
  }

  // 数组随机排序
  function shuffle(arr) {
    var len = arr.length;
    for (var i = 0; i < len - 1; i++) {
      var idx = Math.floor(Math.random() * (len - i));
      var temp = arr[idx];
      arr[idx] = arr[len - i - 1];
      arr[len - i - 1] = temp;
    }
    return arr;
  }

  // 生成扑克牌卡片
  function initPokerCard() {
    var html = '';
    for (var i = 1; i <= pokerAllCount; i++) {
      var sort = pokerAllCount - i + 1;
      var card = pokerAllPet[sort - 1];

      // if(sort == 34){
      // 	card = 'a-3'
      // }else if(sort == 44){
      // 	card = 'a-2'
      // }else if(sort == 54){
      // 	card = 'a-1'
      // }

      html += '<div class="pokerLi" isOpen="no" sort="' + sort + '" card="' + card + '" style="left: ' + (i * 2 - 1) + 'px;">' +
        '<div class="img">' +
        '<img src="img/' + card + '.png" name="face" />' +
        '<img src="img/f-1.png" name="back" />' +
        '</div>' +
        '</div>';
    }
    $('#pokerBox .pokerDeposit').append(html);
  }

  // 首次发牌动画
  function initFirstSendPoker() {
    var pokerLineView = 54; // [ 6, 6, 6, 6, 5, 5, 5, 5, 5, 5 ]
    var pokerLineStart = 1;
    var pokerLineInset = null;
    setTimeout(function () {
      pokerLineInset = setInterval(function () {
        var s = pokerLineStart;
        if (s <= 54) { // 执行首次发牌
          var groupTop = Math.ceil(s / 10);
          var top = (groupTop - 1) * 30;
          var groupLeft = (s - 1) % 10 + 1;
          var left = (groupLeft - 1) * 120;
          animateSendPoker(s, {
            param: {
              top: -612 + top,
              left: left,
              // 'z-index': s,
            },
            group: {
              groupTop: groupTop,
              groupLeft: groupLeft,
            },
          });
          pokerLineStart++;
          pokerSendNum++;
        } else {
          clearInterval(pokerLineInset);
          setTimeout(function () {
            for (var i = pokerLineView - 9; i <= pokerLineView; i++) { // 执行首次翻牌
              // for(var i=pokerLineView-54;i<=pokerLineView;i++){ // 执行首次翻牌
              animateOpenPoker(i);
            }
          }, 200)
        }
      }, 100)
    }, 800)
  }

  // 继续发牌
  function keepSendPoker() {
    var canSend = true;
    $('#pokerBox .pokerLine').each(function () {
      if ($(this).find('.pokerLi').length == 0) {
        canSend = false;
      }
    })
    if (canSend) {
      var lastAllNum = pokerSendNum;
      var pokerLineStart = lastAllNum + 1;
      var pokerLineInset = null;
      pokerLineInset = setInterval(function () {
        var s = pokerLineStart;
        if (s <= lastAllNum + 10) { // 每轮发牌10张
          var groupLeft = s - lastAllNum;
          var left = (groupLeft - 1) * 120;
          var groupTop = $('#pokerBox .pokerLine[group="' + groupLeft + '"] .pokerLi').length + 1;
          var top = (groupTop - 1) * 30;
          animateSendPoker(s, {
            param: {
              top: -612 + top,
              left: left,
              // 'z-index': s,
            },
            group: {
              groupTop: groupTop,
              groupLeft: groupLeft,
            },
          }, function () {
            animateOpenPoker(s);
          });
          pokerLineStart++;
          pokerSendNum++;
        } else {
          clearInterval(pokerLineInset);
        }
      }, 100)
    } else {
      gAlert({
        txt: '不允许在有空列的时候发牌',
      })
    }
  }

  // 执行发牌动画 [s 序号] [j 参数] [c 回调函数]
  function animateSendPoker(s, j, c) {
    var obj = $('#pokerBox .pokerDeposit .pokerLi[sort="' + s + '"]');
    obj.attr(j.group).animate(j.param, 150, function () {
      $('#pokerBox .pokerLine[group="' + j.group.groupLeft + '"]').append(obj.addClass('importantClass').prop('outerHTML'));
      obj.remove();
      if (c) {
        c();
      }
    });
  }

  // 执行翻牌动画 [s 序号] [j 参数] [c 回调函数]
  function animateOpenPoker(s, j, c) {
    $('#pokerBox .pokerLine .pokerLi[sort="' + s + '"]').attr('isOpen', 'yes');
  }

  // 检测是否可以拖动
  function checkCanPickPoker(obj) {
    var result = {
      state: false, // 是否可以拖动 [true 可以] [false 不可以]
      dropGroupTop: 0, // 拖动的卡牌序号
    }
    if ($(obj).attr('isOpen') == 'yes') {
      var groupTop = Number($(obj).attr('groupTop'));
      var groupCardArr = [];
      $(obj).closest('.pokerLine').find('.pokerLi').each(function () {
        if ($(this).attr('groupTop') >= groupTop) {
          var c = $(this).attr('card').split('-');
          groupCardArr.push({
            a: c[0],
            b: Number(c[1]),
            g: $(this).attr('groupTop'),
          });
        }
      })
      // console.log(groupCardArr);

      result.state = true;
      result.dropGroupTop = groupCardArr[0].g;

      if (groupCardArr.length > 1) {
        for (var i = 0; i <= groupCardArr.length - 2; i++) {
          var nowCard = groupCardArr[i];
          var nextCard = groupCardArr[i + 1];
          if (!(nowCard.a == nextCard.a && nowCard.b == nextCard.b + 1)) {
            result.state = false;
            result.dropGroupTop = 0;
          }
        }
      }
    }
    return result;
  }

  // 检测并翻开没有翻开的扑克
  function checkNoOpenPoker() {
    if (pokerSendNum < 54) {
      return false;
    }
    $('#pokerBox .pokerLine').each(function () {
      if ($(this).find('.pokerLi:last').attr('isOpen') == 'no') {
        $(this).find('.pokerLi:last').attr('isOpen', 'yes');
      }
    })
  }

  // 检测是否可以直接收取正确排序的卡牌
  function checkDonePoker() {
    if (pokerSendNum < 54) {
      return false;
    }
    $('#pokerBox .pokerLine .pokerLi[isopen="yes"][card$="-13"]').each(function () {
      var checkBit = $(this).attr('card').split('-')[0];
      var checkTop = Number($(this).attr('groupTop'));
      var pobj = $(this).closest('.pokerLine');
      var isDone = true;
      var pushCard = [$(this).attr('sort')];
      for (var i = 1; i <= 12; i++) {
        var s = pobj.find('.pokerLi[isopen="yes"][groupTop="' + (checkTop + i) + '"]');
        pushCard.push(s.attr('sort'));
        if (pobj.find('.pokerLi[isopen="yes"][groupTop="' + (checkTop + i) + '"]').attr('card') != checkBit + '-' + (13 - i)) {
          isDone = false;
          break;
        }
      }
      if (isDone) {
        pushCard.reverse();
        moveDonePoker(pushCard);
      }
    })
  }

  // 收起正确排序的卡牌
  function moveDonePoker(arr) {
    var endTop = $('#pokerBox .pokerDoneGroup').offset().top;
    var endLeft = $('#pokerBox .pokerDoneGroup').offset().left;
    var html = '';
    $.each(arr, function (a, b) {
      var s = $('#pokerBox .pokerLine .pokerLi[sort="' + b + '"]');
      var top = s.offset().top;
      var left = s.offset().left;
      s.removeClass('importantClass').css({
        'position': 'fixed',
        'left': left,
        'top': top,
      });
      html += s.prop('outerHTML');
      s.animate({top: endTop, left: endLeft}, 250, function () {
        s.remove();
        if (a == arr.length - 1) {
          $('#pokerBox .pokerDoneGroup').append(html);
        }
      });
    });
  }

  // 弹框
  function gAlert(json) {
    var json = $.extend({
      txt: '',
      txtCenter: false,
      btn: '',
      btnCall: null,
      btn2: '',
      btn2Call: null,
      btn3: '',
      btn3Call: null,
    }, json)
    // console.log(json);

    var hasBtn = hasBtn2 = hasBtn3 = false;
    if (json.btn && json.btn != '') {
      hasBtn = true;
    }
    if (json.btn2 && json.btn2 != '') {
      hasBtn2 = true;
    }
    if (json.btn3 && json.btn3 != '') {
      hasBtn3 = true;
    }

    var html = '<div class="gAlert" state="now">' +
      '<div class="txt" style="' + (json.txtCenter ? 'text-align:center;' : '') + '">' + json.txt + '</div>' +
      (hasBtn || hasBtn2 || hasBtn3 ?
        '<div class="tool disFlex heiAuto widAuto">' +
        (hasBtn ? '<div class="btn btn1">' + json.btn + '</div>' : '') +
        (hasBtn2 ? '<div class="btn btn2">' + json.btn2 + '</div>' : '') +
        (hasBtn3 ? '<div class="btn btn3">' + json.btn3 + '</div>' : '') +
        '</div>'
        : '') +
      '</div>';
    $('.gAlert:not(.out)').addClass('out').attr('state', 'out');
    $('body').append(html);
    var sobj = $('.gAlert[state="now"]');
    sobj.find('.btn').click(function () {
      sobj.addClass('out').attr('state', 'out');
      if ($(this).hasClass('btn1') && json.btnCall) {
        json.btnCall();
      } else if ($(this).hasClass('btn2') && json.btn2Call) {
        json.btn2Call();
      } else if ($(this).hasClass('btn3') && json.btn3Call) {
        json.btn3Call();
      }
    })

    if (!hasBtn && !hasBtn2 && !hasBtn3) {
      sobj.css('width', 'auto');
      var width = sobj.outerWidth();
      sobj.css({'margin-left': -width / 2});
      setTimeout(function () {
        sobj.addClass('out').attr('state', 'out');
      }, 2000)
    }

    setTimeout(function () {
      sobj.css('top', 30);
    }, 200)
  }

  // 选择游戏难度
  function chooseGameDifficulty() {
    gAlert({
      txt: '请选择游戏难度',
      txtCenter: true,
      btn: '简单（单色）',
      btnCall: function () {
        pokerDifficult = 1;
        pokerData.type = ['c', 'c', 'c', 'c'];
        initGame();
      },
      btn2: '中等（双色）',
      btn2Call: function () {
        pokerDifficult = 2;
        pokerData.type = ['c', 'd', 'c', 'd'];
        initGame();
      },
      btn3: '困难（四色）',
      btn3Call: function () {
        pokerDifficult = 3;
        pokerData.type = ['a', 'b', 'c', 'd'];
        initGame();
      },
    });
  }

  // 开始游戏
  function initGame() {
    initRandomPoker(); // 生成随机扑克牌数组
    initPokerCard(); // 生成扑克牌卡片
    initFirstSendPoker(); // 触发首次发牌动画
  }

  initView(); // 初始化页面布局
  chooseGameDifficulty(); // 选择游戏难度
</script>
</body>
</html>